package com.ruicar.afs.cloud.batch.controller.config;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.ruicar.afs.cloud.batch.entity.AfsBatchInfo;
import com.ruicar.afs.cloud.batch.entity.AfsBatchJobGroupInfo;
import com.ruicar.afs.cloud.batch.entity.AfsBatchJobStepInfo;
import com.ruicar.afs.cloud.batch.entity.AfsBatchLogStep;
import com.ruicar.afs.cloud.batch.enums.SystemStatus;
import com.ruicar.afs.cloud.batch.service.AfsBatchInfoService;
import com.ruicar.afs.cloud.batch.service.AfsBatchJobGroupInfoService;
import com.ruicar.afs.cloud.batch.service.AfsBatchJobStepInfoService;
import com.ruicar.afs.cloud.batch.service.AfsBatchLogStepService;
import com.ruicar.afs.cloud.common.core.constant.CommonConstants;
import com.ruicar.afs.cloud.common.core.exception.AfsBaseException;
import com.ruicar.afs.cloud.common.core.query.QueryCondition;
import com.ruicar.afs.cloud.common.core.util.IResponse;
import com.ruicar.afs.cloud.common.data.datasource.annotation.DS;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import java.text.MessageFormat;
import java.util.List;
import java.util.stream.Collectors;

@RestController
@RequestMapping("/batchConfig")
@Slf4j
@AllArgsConstructor
public class BatchInfoConfigController {
    private final AfsBatchInfoService afsBatchInfoService;
    private final AfsBatchJobGroupInfoService afsBatchJobGroupInfoService;
    private final AfsBatchJobStepInfoService afsBatchJobStepInfoService;
    private final AfsBatchLogStepService afsBatchLogStepService;

    @GetMapping("/listAllBatchInfo")
    @DS(CommonConstants._BASE_DS_NAME)
    public IResponse<List<AfsBatchInfo>> listAllBatchInfo(){
        return IResponse.success(afsBatchInfoService.list());
    }

    @PostMapping("/editBatchInfo")
    @DS(CommonConstants._BASE_DS_NAME)
    public IResponse<Boolean> editBatchInfo(@RequestBody AfsBatchInfo afsBatchInfo){
        AfsBatchInfo dbEntity = afsBatchInfoService.getById(afsBatchInfo.getSystemName());
        if(dbEntity==null){
            afsBatchInfoService.save(afsBatchInfo);
        }else {
            if(dbEntity.getLiveThreadNum()>0||dbEntity.getSystemStatus()!= SystemStatus.NORMAL){
                throw new AfsBaseException(MessageFormat.format("批量{0}正在运行中不能编辑",afsBatchInfo.getSystemName()));
            }
            afsBatchInfoService.updateById(afsBatchInfo);
        }
        return IResponse.success(Boolean.TRUE);
    }
    @GetMapping("/removeBatchInfo/{systemName}")
    @DS(CommonConstants._BASE_DS_NAME)
    public IResponse<Boolean> removeBatchInfo(@PathVariable String systemName){
        if(afsBatchJobGroupInfoService.count(Wrappers.<AfsBatchJobGroupInfo>lambdaQuery().eq(AfsBatchJobGroupInfo::getSystemName,systemName))>0){
            throw new AfsBaseException(MessageFormat.format("批量{0}存在生效批量组不能删除",systemName));
        }
        if(afsBatchJobStepInfoService.count(Wrappers.<AfsBatchJobStepInfo>lambdaQuery().eq(AfsBatchJobStepInfo::getSystemName,systemName))>0){
            throw new AfsBaseException(MessageFormat.format("批量{0}存在生效批量步骤不能删除",systemName));
        }
        afsBatchInfoService.removeById(systemName);
        return IResponse.success(Boolean.TRUE);
    }

    @GetMapping("/listJobGroup/{systemName}")
    @DS(CommonConstants._BASE_DS_NAME)
    public IResponse<List<AfsBatchJobGroupInfo>> listJobGroup(@PathVariable String systemName){
        List<AfsBatchJobGroupInfo> list =afsBatchJobGroupInfoService.list(Wrappers.<AfsBatchJobGroupInfo>lambdaQuery().eq(AfsBatchJobGroupInfo::getSystemName,systemName).orderByAsc(AfsBatchJobGroupInfo::getShowOrder));
        return IResponse.success(list.stream().filter(group-> StringUtils.isEmpty(group.getDependBatchNo())).collect(Collectors.toList()));
    }

    @GetMapping("/listJobGroupFilter/{systemName}/{filterName}")
    @DS(CommonConstants._BASE_DS_NAME)
    public IResponse<List<AfsBatchJobGroupInfo>> listJobGroupFilterBySelf(@PathVariable String systemName,@PathVariable String filterName){
        List<AfsBatchJobGroupInfo> list =afsBatchJobGroupInfoService.list(Wrappers.<AfsBatchJobGroupInfo>lambdaQuery().eq(AfsBatchJobGroupInfo::getSystemName,systemName).orderByAsc(AfsBatchJobGroupInfo::getShowOrder));
        return IResponse.success(list.stream().filter(group-> !StringUtils.equals(group.getBatchNo(),filterName)&& !StringUtils.equals(group.getDependBatchNo(),filterName)).collect(Collectors.toList()));
    }

    @PostMapping("/editBatchJobInfo")
    @DS(CommonConstants._BASE_DS_NAME)
    @Transactional(rollbackFor = Exception.class)
    public IResponse<Boolean> editBatchJobInfo(@RequestBody AfsBatchJobGroupInfo afsBatchJobGroupInfo){
        AfsBatchInfo dbEntity = afsBatchInfoService.getById(afsBatchJobGroupInfo.getSystemName());
        if(dbEntity.getLiveThreadNum()>0||dbEntity.getSystemStatus()!= SystemStatus.NORMAL){
            throw new AfsBaseException(MessageFormat.format("批量{0}正在运行中不能编辑",afsBatchJobGroupInfo.getSystemName()));
        }
        if(afsBatchJobGroupInfo.getId()==null){
            afsBatchJobGroupInfoService.save(afsBatchJobGroupInfo);
        }else {
            afsBatchJobGroupInfoService.updateById(afsBatchJobGroupInfo);
        }
        return IResponse.success(Boolean.TRUE);
    }


    @PostMapping("/removeBatchJobInfo")
    @DS(CommonConstants._BASE_DS_NAME)
    @Transactional(rollbackFor = Exception.class)
    public IResponse<Boolean> removeBatchJobInfo(@RequestBody AfsBatchJobGroupInfo afsBatchJobGroupInfo){
        AfsBatchInfo dbEntity = afsBatchInfoService.getById(afsBatchJobGroupInfo.getSystemName());
        if(dbEntity.getLiveThreadNum()>0||dbEntity.getSystemStatus()!= SystemStatus.NORMAL){
            throw new AfsBaseException(MessageFormat.format("批量{0}正在运行中不能编辑",afsBatchJobGroupInfo.getSystemName()));
        }
        if(afsBatchJobStepInfoService.count(Wrappers.<AfsBatchJobStepInfo>lambdaQuery().eq(AfsBatchJobStepInfo::getSystemName,afsBatchJobGroupInfo.getSystemName()).eq(AfsBatchJobStepInfo::getBatchNo,afsBatchJobGroupInfo.getBatchNo()))>0){
            throw new AfsBaseException(MessageFormat.format("批量{0}存在生效批量步骤不能删除",afsBatchJobGroupInfo.getBatchName()));
        }
        if(afsBatchJobGroupInfoService.count(Wrappers.<AfsBatchJobGroupInfo>lambdaQuery().eq(AfsBatchJobGroupInfo::getDependBatchNo,afsBatchJobGroupInfo.getBatchNo()))>0){
            throw new AfsBaseException(MessageFormat.format("批量{0}存在被依赖关系不能删除",afsBatchJobGroupInfo.getBatchName()));
        }
        afsBatchJobGroupInfoService.removeById(afsBatchJobGroupInfo.getId());
        return IResponse.success(Boolean.TRUE);
    }


    @GetMapping("/listJobStepFilter/{systemName}/{batchNo}/{filterName}")
    @DS(CommonConstants._BASE_DS_NAME)
    public IResponse<List<AfsBatchJobStepInfo>> listStepList(@PathVariable String systemName,@PathVariable String batchNo,@PathVariable String filterName){
        List<AfsBatchJobStepInfo> list =afsBatchJobStepInfoService.list(Wrappers.<AfsBatchJobStepInfo>lambdaQuery().eq(AfsBatchJobStepInfo::getSystemName,systemName).eq(AfsBatchJobStepInfo::getBatchNo,batchNo).orderByAsc(AfsBatchJobStepInfo::getShowOrder));
        return IResponse.success(list.stream().filter(group-> !StringUtils.equals(group.getStepNo(),filterName)&&!StringUtils.equals(group.getDependStep(),filterName)).collect(Collectors.toList()));
    }


    @PostMapping("/editBatchJobStepInfo")
    @DS(CommonConstants._BASE_DS_NAME)
    @Transactional(rollbackFor = Exception.class)
    public IResponse<Boolean> editBatchJobStepInfo(@RequestBody AfsBatchJobStepInfo afsBatchJobStepInfo){
        AfsBatchInfo dbEntity = afsBatchInfoService.getById(afsBatchJobStepInfo.getSystemName());
        if(dbEntity.getLiveThreadNum()>0||dbEntity.getSystemStatus()!= SystemStatus.NORMAL){
            throw new AfsBaseException(MessageFormat.format("批量{0}正在运行中不能编辑",afsBatchJobStepInfo.getSystemName()));
        }
        if(afsBatchJobStepInfo.getId()==null){
            afsBatchJobStepInfoService.save(afsBatchJobStepInfo);
        }else {
            afsBatchJobStepInfoService.updateById(afsBatchJobStepInfo);
        }
        return IResponse.success(Boolean.TRUE);
    }


    @PostMapping("/removeBatchJobStepInfo")
    @DS(CommonConstants._BASE_DS_NAME)
    @Transactional(rollbackFor = Exception.class)
    public IResponse<Boolean> removeBatchJobStepInfo(@RequestBody AfsBatchJobStepInfo afsBatchJobStepInfo){
        AfsBatchInfo dbEntity = afsBatchInfoService.getById(afsBatchJobStepInfo.getSystemName());
        if(dbEntity.getLiveThreadNum()>0||dbEntity.getSystemStatus()!= SystemStatus.NORMAL){
            throw new AfsBaseException(MessageFormat.format("批量{0}正在运行中不能编辑",afsBatchJobStepInfo.getSystemName()));
        }
        if(afsBatchJobStepInfoService.count(Wrappers.<AfsBatchJobStepInfo>lambdaQuery().eq(AfsBatchJobStepInfo::getDependStep,afsBatchJobStepInfo.getStepNo()))>0){
            throw new AfsBaseException(MessageFormat.format("批量步骤{0}存在被依赖关系不能删除",afsBatchJobStepInfo.getStepName()));
        }
        afsBatchJobStepInfoService.removeById(afsBatchJobStepInfo.getId());
        return IResponse.success(Boolean.TRUE);
    }


    @PostMapping("/queryStepLogs")
    @DS(CommonConstants._BASE_DS_NAME)
    public IResponse<Page<AfsBatchLogStep>> listLog(@RequestBody QueryCondition<AfsBatchLogStep> condition){
        LambdaQueryWrapper wrapper= Wrappers.<AfsBatchLogStep>lambdaQuery()
                .eq(StringUtils.isNotEmpty(condition.getCondition().getBatchDate()),AfsBatchLogStep::getBatchDate,condition.getCondition().getBatchDate())
                .eq(StringUtils.isNotEmpty(condition.getCondition().getBatchNo()),AfsBatchLogStep::getBatchNo,condition.getCondition().getBatchNo())
                .eq(StringUtils.isNotEmpty(condition.getCondition().getStepNo()),AfsBatchLogStep::getStepNo,condition.getCondition().getStepNo())
                .eq(condition.getCondition().getStepStatus()!=null,AfsBatchLogStep::getStepStatus,condition.getCondition().getStepStatus())
                .eq(StringUtils.isNotEmpty(condition.getCondition().getSystemName()),AfsBatchLogStep::getSystemName,condition.getCondition().getSystemName())
                ;
        return IResponse.success(afsBatchLogStepService.page(condition.page(),wrapper));
    }

}
